#include "InSdkIniConfig.h"

#define DEF_TAG "IniConf"

pthread_mutex_t g_InSdkAppCfg_IntMutex;
pthread_mutex_t g_InSdkAppCfg_StrMutex;
pthread_mutex_t g_InSdkBasicCfg_Mutex;

StSdkBasicCfgAll g_InSdkBasicCfg_AllInfo[BASIC_CFG_MAX] = {
    {BASIC_CFG_FLIP, "cfg:flip"},
    {BASIC_CFG_IRCUT_REVERSE, "cfg:ircut_reverse"},
    {BASIC_CFG_TIMEZONE_SEC, "cfg:tz_sec"},
    {BASIC_CFG_MIC_DISABLE, "cfg:mic_disable"},
    {BASIC_CFG_IRCUT, "cfg:ircut"},
    {BASIC_CFG_SPK_VOL, "cfg:spk_vol"},
    {BASIC_CFG_MIC_VOL, "cfg:mic_vol"},
    {BASIC_CFG_SPK_GAIN, "cfg:spk_gain"},
    {BASIC_CFG_MIC_GAIN, "cfg:mic_gain"},
    {BASIC_CFG_LINK_LED, "cfg:link_led"},
    {BASIC_CFG_WATCH_LED, "cfg:watch_led"},
    {BASIC_CFG_NIGHT_MODE, "cfg:night_mode"},
    {BASIC_CFG_NIGHT_MODE_SW, "cfg:night_mode_sw"},
};
Com_s32 g_InSdkBasicCfg_Val[BASIC_CFG_MAX];

Com_void InSdkIniCfg_Recover(struct config *conf, Com_ps8 key)
{
    PRT_WARN(DEF_TAG, "no %s\n", key);
    conf_set_string(conf, key, "0");
    conf_save(conf);
}

Com_s8 InSdkBasicCfg_GetInfo(Com_void)
{
    Com_s32 i;

    memset(g_InSdkBasicCfg_Val, 0, sizeof(g_InSdkBasicCfg_Val));

    struct config *conf = conf_load(DEF_INI_BASIC_CONFIG);
    if (conf_get_string(conf, "cfg") == NULL)
    {
        conf_unload(conf);
        return DEF_COM_FAILED;
    }

    for (i = 0; i < BASIC_CFG_MAX; i++)
    {
        g_InSdkBasicCfg_Val[i] = conf_get_int(conf, g_InSdkBasicCfg_AllInfo[i].string);
        PRT_WARN(DEF_TAG, "Basic Cfg Val[%d]=%d\n", i, g_InSdkBasicCfg_Val[i]);
    }

    conf_unload(conf);
    return DEF_COM_SUCCESS;
}

Com_void InSdkBasicCfg_Init(Com_void)
{
    Com_s32 ret;
    Com_s32 i;
    Com_s8 get_sys_basic_flag = DEF_COM_FAILED;

    get_sys_basic_flag = InSdkBasicCfg_GetInfo();
    Ext_InComFile_JudgeCreat(DEF_INI_BASIC_CONFIG);
    struct config *conf = conf_load(DEF_INI_BASIC_CONFIG);
    if (conf_get_string(conf, "cfg") == NULL)
    {
        InSdkIniCfg_Recover(conf, "cfg");
    }

    for (i = 0; i < BASIC_CFG_MAX; i++)
    {
        if ((g_InSdkBasicCfg_Val[i] != -1) && (get_sys_basic_flag == DEF_COM_SUCCESS))
        {
            Com_s8 val_str[32];

            memset(val_str, 0, sizeof(val_str));
            sprintf(val_str, "%d", g_InSdkBasicCfg_Val[i]);
            conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, val_str);
            PRT_WARN(DEF_TAG, "set basic[%d] %s\n", i, val_str);
        }
        else
        {
            ret = conf_get_int(conf, g_InSdkBasicCfg_AllInfo[i].string);
            if (ret == -1)
            {
                switch (i)
                {
                case BASIC_CFG_FLIP:
                {
#if CMAKE_DEFAULT_FLIP
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "1");
#else
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "0");
#endif
                }
                break;

                case BASIC_CFG_IRCUT_REVERSE:
                {
#if CMAKE_IRCUT_REVERSE
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "1");
#else
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "0");
#endif
                }
                break;

                case BASIC_CFG_TIMEZONE_SEC:
                {
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "28800");
                }
                break;

                case BASIC_CFG_MIC_DISABLE:
                {
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "0");
                }
                break;

                case BASIC_CFG_IRCUT:
                {
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "1");
                }
                break;

                case BASIC_CFG_NIGHT_MODE:
                {
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "2");
                }
                break;

                case BASIC_CFG_NIGHT_MODE_SW:
                {
                    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[i].string, "2");
                }
                break;

                default:
                {
                }
                break;
                }
            }
        }
    }

    conf_save(conf);
    conf_unload(conf);
}

Com_void InSdkAppCfg_Check(Com_void)
{
    Com_s32 ret = 0;

    InSdkBasicCfg_Init();
    Ext_InSdkBasicCfg_GetAll();

    Ext_InComFile_JudgeCreat(DEF_INI_DEV_CONFIG);
    struct config *conf = conf_load(DEF_INI_DEV_CONFIG);
    if (conf_get_string(conf, "cfg") == NULL)
    {
        InSdkIniCfg_Recover(conf, "cfg");
    }

    ret = conf_get_int(conf, "cfg:spk_volume");
    if (ret == -1)
    {
        conf_set_string(conf, "cfg:spk_volume", "6");
    }

    ret = conf_get_int(conf, "cfg:md_time_switch");
    if (ret == -1)
    {
        conf_set_string(conf, "cfg:md_time_switch", "0");
    }

    ret = conf_get_int(conf, "cfg:alarm_zone");
    if (ret == -1)
    {
        conf_set_string(conf, "cfg:alarm_zone", "0");
    }

    if (conf_get_string(conf, "cfg:motion_time") == NULL)
    {
        conf_set_string(conf, "cfg:motion_time", "00002359");
    }

    if (conf_get_string(conf, "cfg:alarm_zone_draw") == NULL)
    {
        conf_set_string(conf, "cfg:alarm_zone_draw", "off");
    }

    ret = conf_get_int(conf, "cfg:ipc_contrast");
    if (ret == -1)
    {
        conf_set_string(conf, "cfg:ipc_contrast", "50");
    }

    ret = conf_get_int(conf, "cfg:ipc_bright");
    if (ret == -1)
    {
        conf_set_string(conf, "cfg:ipc_bright", "50");
    }

    ret = conf_get_int(conf, "cfg:sleep_mode");
    if (ret == -1)
    {
        conf_set_string(conf, "cfg:sleep_mode", "0");
    }

    ret = conf_get_int(conf, "cfg:anti_flicker");
    if (ret == -1)
    {
        conf_set_string(conf, "cfg:anti_flicker", "0");
    }

    conf_save(conf);
    conf_unload(conf);
}

Com_void Ext_InSdkBasicCfg_SetVal(EComBasicCfg key, Com_s32 val)
{
    pthread_mutex_lock(&g_InSdkBasicCfg_Mutex);

    Com_s8 buff[32];

    memset(buff, 0, sizeof(buff));

    struct config *conf = conf_load(DEF_INI_BASIC_CONFIG);
    snprintf(buff, sizeof(buff), "%d", val);
    conf_set_string(conf, g_InSdkBasicCfg_AllInfo[key].string, buff);
    conf_save(conf);
    conf_unload(conf);

    g_InSdkBasicCfg_Val[key] = val;
    pthread_mutex_unlock(&g_InSdkBasicCfg_Mutex);
}

Com_void Ext_InSdkBasicCfg_GetAll(Com_void)
{
    pthread_mutex_lock(&g_InSdkBasicCfg_Mutex);

    Com_s32 i = 0;
    struct config *conf = conf_load(DEF_INI_BASIC_CONFIG);

    for (i = 0; i < BASIC_CFG_MAX; i++)
    {
        g_InSdkBasicCfg_Val[i] = conf_get_int(conf, g_InSdkBasicCfg_AllInfo[i].string);
    }

    conf_unload(conf);
    pthread_mutex_unlock(&g_InSdkBasicCfg_Mutex);
}

Com_s32 Ext_InSdkBasicCfg_GetVal(EComBasicCfg dp)
{
    return g_InSdkBasicCfg_Val[dp];
}

Com_void Ext_InSdkAppCfg_SetInt(EnSdkAppCfg dp, Com_s32 val)
{
    pthread_mutex_lock(&g_InSdkAppCfg_IntMutex);

    char buff[32];
    memset(buff, 0, sizeof(buff));

    struct config *conf = conf_load(DEF_INI_DEV_CONFIG);
    snprintf(buff, sizeof(buff), "%d", val);

    switch (dp)
    {
    case APP_CFG_SPK_VOLUME:
        conf_set_string(conf, "cfg:spk_volume", buff);
        break;

    case APP_CFG_MD_TIME_SWITCH:
        conf_set_string(conf, "cfg:md_time_switch", buff);
        break;

    case APP_CFG_ALARM_ZONE:
        conf_set_string(conf, "cfg:alarm_zone", buff);
        break;

    case APP_CFG_IPC_CONTRAST:
        conf_set_string(conf, "cfg:ipc_contrast", buff);
        break;

    case APP_CFG_IPC_BRIGHT:
        conf_set_string(conf, "cfg:ipc_bright", buff);
        break;

    case APP_CFG_SLEEP_MODE:
        conf_set_string(conf, "cfg:sleep_mode", buff);
        break;

    case APP_CFG_ANTI_FLICKER:
        conf_set_string(conf, "cfg:anti_flicker", buff);
        break;

    default:
        PRT_WARN(DEF_TAG, "no this set dpid\n");
        break;
    }

    conf_save(conf);
    conf_unload(conf);
    pthread_mutex_unlock(&g_InSdkAppCfg_IntMutex);
}

Com_s32 Ext_InSdkAppCfg_GetInt(EnSdkAppCfg dp)
{
    pthread_mutex_lock(&g_InSdkAppCfg_IntMutex);

    Com_s32 val = 0;
    struct config *conf = conf_load(DEF_INI_DEV_CONFIG);

    switch (dp)
    {
    case APP_CFG_SPK_VOLUME:
        val = conf_get_int(conf, "cfg:spk_volume");
        break;

    case APP_CFG_MD_TIME_SWITCH:
        val = conf_get_int(conf, "cfg:md_time_switch");
        break;

    case APP_CFG_ALARM_ZONE:
        val = conf_get_int(conf, "cfg:alarm_zone");
        break;

    case APP_CFG_IPC_CONTRAST:
        val = conf_get_int(conf, "cfg:ipc_contrast");
        break;

    case APP_CFG_IPC_BRIGHT:
        val = conf_get_int(conf, "cfg:ipc_bright");
        break;

    case APP_CFG_SLEEP_MODE:
        val = conf_get_int(conf, "cfg:sleep_mode");
        break;

    case APP_CFG_ANTI_FLICKER:
        val = conf_get_int(conf, "cfg:anti_flicker");
        break;

    default:
        break;
    }

    conf_unload(conf);
    pthread_mutex_unlock(&g_InSdkAppCfg_IntMutex);
    return val;
}

Com_void Ext_InSdkAppCfg_SetStr(EnSdkAppCfg dp, Com_ps8 buf)
{
    pthread_mutex_lock(&g_InSdkAppCfg_StrMutex);

    struct config *conf = conf_load(DEF_INI_DEV_CONFIG);

    switch (dp)
    {
    case APP_CFG_MOTION_TIME:
        conf_set_string(conf, "cfg:motion_time", buf);
        break;

    case APP_CFG_ALARM_ZONE_DRAW:
        conf_set_string(conf, "cfg:alarm_zone_draw", buf);
        break;

    default:
        PRT_INFO(DEF_TAG, "no this set dpid\n");
        break;
    }

    conf_save(conf);
    conf_unload(conf);
    pthread_mutex_unlock(&g_InSdkAppCfg_StrMutex);
}

Com_void Ext_InSdkAppCfg_GetStr(EnSdkAppCfg dp, _OUT Com_ps8 buf)
{
    pthread_mutex_lock(&g_InSdkAppCfg_StrMutex);

    Com_s32 ret = 0;
    struct config *conf = conf_load(DEF_INI_DEV_CONFIG);

    switch (dp)
    {
    case APP_CFG_MOTION_TIME:
    {
        if (conf_get_string(conf, "cfg:motion_time") != NULL)
        {
            strcpy(buf, conf_get_string(conf, "motion_time"));
        }
        else
        {
            ret = -1;
        }
    }
    break;

    case APP_CFG_ALARM_ZONE_DRAW:
    {
        if (conf_get_string(conf, "cfg:alarm_zone_draw") != NULL)
        {
            strcpy(buf, conf_get_string(conf, "alarm_zone_draw"));
        }
        else
        {
            ret = -1;
        }
    }
    break;

    default:
        break;
    }

    if (ret == -1)
    {
        strcpy(buf, "01");
    }

    conf_unload(conf);
    pthread_mutex_unlock(&g_InSdkAppCfg_StrMutex);
}

Com_void Ext_InSdkIniCfg_LockInit(Com_void)
{
    pthread_mutex_init(&g_InSdkAppCfg_IntMutex, NULL);
    pthread_mutex_init(&g_InSdkAppCfg_StrMutex, NULL);
    pthread_mutex_init(&g_InSdkBasicCfg_Mutex, NULL);
}

Com_void Ext_InSdkIniCfg_LockDestroy(Com_void)
{
    pthread_mutex_destroy(&g_InSdkAppCfg_IntMutex);
    pthread_mutex_destroy(&g_InSdkAppCfg_StrMutex);
    pthread_mutex_destroy(&g_InSdkBasicCfg_Mutex);
}

Com_void InSdkIniCfgCheck(Com_ps8 file)
{
    struct config *conf = NULL;
app_again:
    conf = conf_load(file);
    if(conf == NULL)
    {
        Ext_InComFile_JudgeRemove(file);
        Ext_InComFile_JudgeCreat(file);
        goto app_again;
    }

    conf_unload(conf);
}

Com_void Ext_InSdkIniCfg_Init(Com_void)
{
    InSdkIniCfgCheck(DEF_INI_BASIC_CONFIG);
    InSdkIniCfgCheck(DEF_INI_DEV_CONFIG);
    InSdkAppCfg_Check();
}
